﻿using Devonline.Communication.Abstractions;
using Devonline.Communication.Messages;
using Devonline.Entity;
using Microsoft.Extensions.Logging;

namespace CombinationCommunicator;

/// <summary>
/// 两种通讯器融合转发的形式构成的新的通讯器
/// </summary>
internal class Communicator : MessageCommunicator, IMessageCommunicator
{
    /// <summary>
    /// 定义第二个通讯器
    /// </summary>
    private readonly ICommunicator _communicator;
    /// <summary>
    /// 构造函数
    /// </summary>
    /// <param name="logger"></param>
    /// <param name="communicator"></param>
    /// <param name="messageOptions"></param>
    public Communicator(ILogger<Communicator> logger, ICommunicator communicator, MessageOptions messageOptions) : base(logger, messageOptions)
    {
        _communicator = communicator;
    }

    /// <summary>
    /// 启动融合通讯器
    /// </summary>
    /// <returns></returns>
    public override async Task StartAsync()
    {
        await base.StartAsync();
        await _communicator.StartAsync();
    }
    /// <summary>
    /// 关闭融合通讯器
    /// </summary>
    /// <returns></returns>
    public override async Task StopAsync()
    {
        _communicator.Receive -= OnReceiveData;
        await _communicator.StopAsync();
        await base.StopAsync();
    }

    /// <summary>
    /// 初始化融合通讯器
    /// 设定第二个通讯器收到消息后, 使用第一个通讯器将消息中转发出
    /// </summary>
    protected override void OnInitial()
    {
        _communicator.Receive += OnReceiveData;
        base.OnInitial();
    }
    /// <summary>
    /// 重写消息接收方法
    /// 即第一个通讯器收到消息, 使用第二个通讯器将消息中转发出
    /// </summary>
    /// <param name="message"></param>
    protected override void OnReceive(Message message)
    {
        if (!string.IsNullOrWhiteSpace(message.Content))
        {
            Task.Run(async () => await _communicator.SendAsync(message.Content));
        }

        base.OnReceive(message);
    }

    /// <summary>
    /// 第二个通讯器接受数据后的事件委托处理方法
    /// 第二个通讯器收到消息后, 使用第一个通讯器将消息中转发出
    /// </summary>
    /// <param name="sender"></param>
    /// <param name="message"></param>
    private async void OnReceiveData(object? sender, string message) => await SendAsync(message);
}